/*
 * Copyright 2023-2085 xujin <ceo@itgrail.com>
 *
 * Licensed under the Grail License, Version 1.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 * https://itgrail.com/docs?id=3&catalogId=87
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */
package com.itgrail.pilot.app.command.query;

import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.google.common.base.Preconditions;
import com.itgrail.pilot.app.command.cmo.query.DetailOkrAlignTreeCmd;
import com.itgrail.pilot.app.command.co.OkrAlignTreeCO;
import com.itgrail.pilot.domain.user.contant.OkrConstants;
import com.itgrail.pilot.infrastructure.tunnel.db.dao.ObjectiveMapper;
import com.itgrail.pilot.infrastructure.tunnel.db.dao.UserMapper;
import com.itgrail.pilot.infrastructure.tunnel.db.dao.UserOkrAlignMapper;
import com.itgrail.pilot.infrastructure.tunnel.db.dataobject.ObjectiveDO;
import com.itgrail.pilot.infrastructure.tunnel.db.dataobject.UserDO;
import com.itgrail.pilot.infrastructure.tunnel.db.dataobject.UserOkrAlignDO;
import org.apache.commons.collections.CollectionUtils;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import com.itgrail.grail.cqrs.annotation.CmdHandler;
import com.itgrail.grail.cqrs.command.CommandExecutorI;
import com.itgrail.grail.dto.ResultData;

import java.util.ArrayList;
import java.util.List;


@CmdHandler
public class DetailOkrAlignTreeCmdExe implements CommandExecutorI<ResultData, DetailOkrAlignTreeCmd> {

    @Autowired
    private UserOkrAlignMapper userOkrAlignMapper;

    @Autowired
    private ObjectiveMapper objectiveMapper;

    @Autowired
    private UserMapper userMapper;

    @Override
    public ResultData execute(DetailOkrAlignTreeCmd cmd) {
        ResultData resultData = ResultData.success(null);
        check(cmd);
        List<OkrAlignTreeCO> okrAlignTree = getOkrAlignTree(cmd);
        resultData.setData(okrAlignTree);
        return resultData;
    }

    protected boolean check(DetailOkrAlignTreeCmd cmd) {
        Preconditions.checkNotNull(cmd, "cmd不能为null");
        Preconditions.checkNotNull(cmd.getOkrPeriodId(), "OKR周期没有添加,请添加OKR周期之后再操作!");
        return true;
    }

    private List<OkrAlignTreeCO> getOkrAlignTree(DetailOkrAlignTreeCmd cmd) {
        List<OkrAlignTreeCO> alignTreeCOS = new ArrayList<>();
        //根据当前周期和用户id 查询出当前用户的所有okr对齐的okr  级联查询
        QueryWrapper<ObjectiveDO> objectiveDOQueryWrapper = new QueryWrapper<>();
        objectiveDOQueryWrapper.eq("okr_period_id", cmd.getOkrPeriodId());
        objectiveDOQueryWrapper.eq("created", cmd.getUserId());
        objectiveDOQueryWrapper.eq("deleted", OkrConstants.NOT_DELETED);
        //查询用户当前周期下的所有O
        List<ObjectiveDO> objectiveDOS = objectiveMapper.selectList(objectiveDOQueryWrapper);
        //根据每个O查询
        if (CollectionUtils.isNotEmpty(objectiveDOS)) {
            for (int i = 0; i < objectiveDOS.size(); i++) {
                ObjectiveDO objectiveDO = objectiveDOS.get(i);
                List<OkrAlignTreeCO> upTree = upTree(objectiveDO);
                alignTreeCOS.addAll(upTree);
            }
        }
        return alignTreeCOS;
    }

    private List<OkrAlignTreeCO> upTree(ObjectiveDO objectiveDO) {
        List<OkrAlignTreeCO> treeCOS = new ArrayList<>();
        QueryWrapper<UserOkrAlignDO> queryWrapper = new QueryWrapper<>();
        queryWrapper.eq("accept_objective_id", objectiveDO.getId());
        queryWrapper.eq("okr_period", objectiveDO.getOkrPeriodId());
        //拿到所有向当前O对齐的O
        List<UserOkrAlignDO> alignDOList = userOkrAlignMapper.selectList(queryWrapper);
        //拿到O
        OkrAlignTreeCO treeCO = new OkrAlignTreeCO();
        QueryWrapper<UserDO> dingUserDOQueryWrapper = new QueryWrapper<>();
        dingUserDOQueryWrapper.eq("user_id", objectiveDO.getCreated());
        UserDO objectiveUser = userMapper.selectOne(dingUserDOQueryWrapper);
        if (null != objectiveUser) {
            if (StringUtils.isNotEmpty(objectiveUser.getDingUrl())) {
                treeCO.setUrl(objectiveUser.getDingUrl());
            }
            if (StringUtils.isNotEmpty(objectiveUser.getName())) {
                treeCO.setPersonName(objectiveUser.getName());
            }
        }

        //拿到当前O对齐的o
        treeCO.setId(objectiveDO.getId());
        treeCO.setObjectiveText(objectiveDO.getName());
        List<OkrAlignTreeCO> children = new ArrayList<>();

        treeCO.setCreated(objectiveDO.getCreated());
        if (CollectionUtils.isNotEmpty(alignDOList)) {
            alignDOList.forEach(x -> {
                ObjectiveDO acceptObjective = objectiveMapper.selectById(x.getStartObjectiveId());
                children.addAll(upTree(acceptObjective));
            });
        }
        treeCO.setChildren(children);
        treeCO.setAlignCount(children.size());
        treeCOS.add(treeCO);
        return treeCOS;
    }


/*    private List<OkrAlignTreeCO> getOkrAlignTree(DetailOkrAlignTreeCmd cmd) {
        List<OkrAlignTreeCO> alignTreeCOS = new ArrayList<>();
        //根据当前周期和用户id 查询出当前用户的所有okr对齐的okr  级联查询
        QueryWrapper<ObjectiveDO> objectiveDOQueryWrapper = new QueryWrapper<>();
        objectiveDOQueryWrapper.eq("okr_period_id", cmd.getOkrPeriodId());
        objectiveDOQueryWrapper.eq("created", cmd.getUserId());
        objectiveDOQueryWrapper.eq("deleted", OkrConstants.NOT_DELETED);
        //查询用户当前周期下的所有O
        List<ObjectiveDO> objectiveDOS = objectiveMapper.selectList(objectiveDOQueryWrapper);
        //根据每个O查询
        if (CollectionUtils.isNotEmpty(objectiveDOS)) {
            for (int i = 0; i < objectiveDOS.size(); i++) {
                ObjectiveDO objectiveDO = objectiveDOS.get(i);
                List<OkrAlignTreeCO> upTree = upTree(objectiveDO);
                alignTreeCOS.addAll(upTree);
            }
        }
        alignTreeCOS = alignTreeCOS.stream().distinct().collect(Collectors.toList());
        return alignTreeCOS;
    }

    *//**
     * 根据O信息 向下找对齐视图
     * @return
     *//*
    private List<OkrAlignTreeCO> downTree(ObjectiveDO objectiveDO ) {
        List<OkrAlignTreeCO> treeCOS = new ArrayList<>();
        QueryWrapper<UserOkrAlignDO> queryWrapper = new QueryWrapper<>();
        queryWrapper.eq("start_objective_id", objectiveDO.getId());
        queryWrapper.eq("okr_period", objectiveDO.getOkrPeriodId());
        List<UserOkrAlignDO> alignDOList = userOkrAlignMapper.selectList(queryWrapper);
        if (CollectionUtils.isNotEmpty(alignDOList)) {
            alignDOList.forEach(x->{
                ObjectiveDO acceptObjective = objectiveMapper.selectById(x.getAcceptObjectiveId());
                QueryWrapper<DingUserDO> dingUserDOQueryWrapper = new QueryWrapper<>();
                dingUserDOQueryWrapper.eq("user_id", acceptObjective.getCreated());
                DingUserDO objectiveUser = userMapper.selectOne(dingUserDOQueryWrapper);
                OkrAlignTreeCO treeCO = new OkrAlignTreeCO();
                if (null != objectiveUser) {
                    if (StringUtils.isNotEmpty(objectiveUser.getDingUrl())) {
                        treeCO.setUrl(objectiveUser.getDingUrl());
                    }
                    if (StringUtils.isNotEmpty(objectiveUser.getName())) {
                        treeCO.setPersonName(objectiveUser.getName());
                    }
                }
                treeCO.setAlignCount(acceptObjective.getAlignCount());
                //拿到当前O对齐的o
                treeCO.setId(acceptObjective.getId());
                treeCO.setObjectiveText(acceptObjective.getName());
                treeCO.setChildren(downTree(acceptObjective));
                treeCO.setCreated(acceptObjective.getCreated());
                treeCOS.add(treeCO);
            });
        }
        return treeCOS;
    }

    *//**
     * 向上找对齐的视图
     * @return
     *//*
    private List<OkrAlignTreeCO> upTree(ObjectiveDO objectiveDO) {
        List<OkrAlignTreeCO> treeCOS = new ArrayList<>();
        QueryWrapper<UserOkrAlignDO> queryWrapper = new QueryWrapper<>();
        queryWrapper.eq("accept_objective_id", objectiveDO.getId());
        queryWrapper.eq("okr_period", objectiveDO.getOkrPeriodId());
        List<UserOkrAlignDO> alignDOList = userOkrAlignMapper.selectList(queryWrapper);

        if (CollectionUtils.isNotEmpty(alignDOList)) {
            //向上查询O
            alignDOList.forEach(x -> {
                ObjectiveDO acceptObjective = objectiveMapper.selectById(x.getStartObjectiveId());
                QueryWrapper<DingUserDO> dingUserDOQueryWrapper = new QueryWrapper<>();
                dingUserDOQueryWrapper.eq("user_id", acceptObjective.getCreated());
                DingUserDO objectiveUser = userMapper.selectOne(dingUserDOQueryWrapper);
                OkrAlignTreeCO treeCO = new OkrAlignTreeCO();
                if (null != objectiveUser) {
                    if (StringUtils.isNotEmpty(objectiveUser.getDingUrl())) {
                        treeCO.setUrl(objectiveUser.getDingUrl());
                    }
                    if (StringUtils.isNotEmpty(objectiveUser.getName())) {
                        treeCO.setPersonName(objectiveUser.getName());
                    }
                }
                treeCO.setAlignCount(acceptObjective.getAlignCount());
                //拿到当前O对齐的o
                treeCO.setId(acceptObjective.getId());
                treeCO.setObjectiveText(acceptObjective.getName());
                treeCO.setChildren(downTree(acceptObjective));
                treeCO.setCreated(acceptObjective.getCreated());
                treeCOS.add(treeCO);
            });
        } else {
            //向下查询O
            OkrAlignTreeCO treeCO = new OkrAlignTreeCO();
            QueryWrapper<DingUserDO> dingUserDOQueryWrapper = new QueryWrapper<>();
            dingUserDOQueryWrapper.eq("user_id", objectiveDO.getCreated());
            DingUserDO objectiveUser = userMapper.selectOne(dingUserDOQueryWrapper);
            if (null != objectiveUser) {
                if (StringUtils.isNotEmpty(objectiveUser.getDingUrl())) {
                    treeCO.setUrl(objectiveUser.getDingUrl());
                }
                if (StringUtils.isNotEmpty(objectiveUser.getName())) {
                    treeCO.setPersonName(objectiveUser.getName());
                }
            }
            treeCO.setAlignCount(objectiveDO.getAlignCount());
            //拿到当前O对齐的o
            treeCO.setId(objectiveDO.getId());
            treeCO.setObjectiveText(objectiveDO.getName());
            treeCO.setChildren(downTree(objectiveDO));
            treeCO.setCreated(objectiveDO.getCreated());
            treeCOS.add(treeCO);
        }
        return treeCOS;
    }*/
}
